"""
将对象组合成树形结构以表示“部分-整体”的层次结构(特别是结构是递归的)，组合模式使得用户对单个对象和组合对象的使用具有一致性。

角色：
    抽象组件（Component）
    叶子组件（Leaf）
    复合组件（Composite）
    客户端（Client）

其实就是：
    1、把部分组合成一个整体，就像一个线段包含二个点
"""

from abc import ABCMeta, abstractmethod


# 抽象组件（Component）
class Graphic(metaclass=ABCMeta):
    @abstractmethod
    def draw(self):
        pass


# 叶子组件（Leaf）
class Point(Graphic):
    """点"""

    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return "点(%d,%d)" % (self.x, self.y)

    def draw(self):
        print(str(self))


# 叶子组件（Leaf）
class Line(Graphic):
    """线"""

    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return '线段[(%s,%s)]' % (self.x, self.y)

    def draw(self):
        print(str(self))


# 复合组件（Composite）
class Composite(Graphic):
    def __init__(self, iterable):
        self.children = []
        for g in iterable:
            self.add(g)

    def add(self, graphic):
        self.children.append(graphic)

    def draw(self):
        for g in self.children:
            g.draw()


# 简单图形
print('------简单图形------')
p = Point(1, 2)
l1 = Line(Point(1, 2), Point(3, 4))  # 一个线段包含二个点
l2 = Line(Point(5, 6), Point(7, 8))
print(p)
print(l1, l2)
print('------复合图形(p,l1,l2)------')
# 复合图形
pic = Composite([p, l1, l2])  # 一个复合图形包含一个点，二个线段
pic.draw()
